﻿using UnityEngine;
using System.Collections;

public class PanelSingleton<T> : UIPanel where T:UIPanel
{
    // 单件子类实例
    private static T _instance;
    public static T Instance
    {
        get { return GetInstance(); }
    }

    // 在单件中，每个物件的destroyed标志设计上应该分割在不同的存储个空间中，因此，忽略R#的这个提示
    // ReSharper disable once StaticFieldInGenericType
    //private static bool _destroyed;

    public static bool IsValidate()
    {
        return _instance != null;
    }

    /// <summary>
    ///     获得单件实例，查询场景中是否有该种类型，如果有存储静态变量，如果没有，构建一个带有这个component的gameobject
    ///     这种单件实例的GameObject直接挂接在bootroot节点下，在场景中的生命周期和游戏生命周期相同，创建这个单件实例的模块
    ///     必须通过DestroyInstance自行管理单件的生命周期
    /// </summary>
    /// <returns>返回单件实例</returns>
    public static T GetInstance()
    {

        if (_instance == null)
        {
            var name = typeof (T).Name;
            var panelPrefab = ResourceManager.Instance.LoadPrefab(name);
            if (panelPrefab != null)
            {
                _instance = panelPrefab.transform.GetOrAddComponent<T>();
                UICanvasMgr.Instance.AddPanel(panelPrefab);
            }
        }

        return _instance;
    }

    /// <summary>
    ///     删除单件实例,这种继承关系的单件生命周期应该由模块显示管理
    /// </summary>
    public static void DestroyInstance()
    {
        if (_instance != null)
            Destroy(_instance.gameObject);

        _instance = null;
    }

    /// <summary>
    ///     Awake消息，确保单件实例的唯一性,删除之前的instance,要确保子类不要使用Awake
    /// </summary>
    protected void Awake()
    {
        if (IsValidate())
        {
            Destroy(gameObject);
            return;
        }

        if (_instance != null && _instance.gameObject != gameObject)
        {
            Destroy(_instance.gameObject);
            _instance = GetComponent<T>();
        }
        else if (_instance == null)
            _instance = GetComponent<T>();
    }

    /// <summary>
    ///     OnDestroy消息，确保单件的静态实例会随着GameObject销毁
    /// </summary>
    protected virtual void OnDestroy()
    {
        if (_instance != null && _instance.gameObject == gameObject) _instance = null;
    }


    public override void Open()
    {
        Show();
    }

    public override void Close()
    {
        Hide();
    }

    public override void Show()
    {
        gameObject.SetActive(true);
    }

    public override void Hide()
    {
        gameObject.SetActive(false);
    }
}
